package jnpf.service.impl;

import jnpf.entity.*;
import jnpf.mapper.ThemeFileMapper;
import jnpf.service.*;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import jnpf.model.themefile.*;
import cn.hutool.core.util.ObjectUtil;
import jnpf.util.GeneraterSwapUtil;

import java.lang.reflect.Field;

import com.baomidou.mybatisplus.annotation.TableField;
import jnpf.model.QueryModel;

import java.util.stream.Collectors;

import jnpf.base.model.ColumnDataModel;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.core.metadata.IPage;
import jnpf.database.model.superQuery.SuperJsonModel;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import jnpf.util.*;

import java.util.*;

import jnpf.base.UserInfo;
import jnpf.permission.entity.UserEntity;

/**
 * themeFile
 * 版本： V3.5
 * 版权： 引迈信息技术有限公司（https://www.jnpfsoft.com）
 * 作者： JNPF开发平台组
 * 日期： 2025-05-20
 */
@Service
public class ThemeFileServiceImpl extends ServiceImpl<ThemeFileMapper, ThemeFileEntity> implements ThemeFileService {
    @Autowired
    private GeneraterSwapUtil generaterSwapUtil;

    @Autowired
    private UserProvider userProvider;

    @Override
    public List<ThemeFileEntity> getList(ThemeFilePagination themeFilePagination) {
        return getTypeList(themeFilePagination, themeFilePagination.getDataType());
    }

    /**
     * 列表查询
     */
    @Override
    public List<ThemeFileEntity> getTypeList(ThemeFilePagination themeFilePagination, String dataType) {
        String userId = userProvider.get().getUserId();
        List<String> AllIdList = new ArrayList();
        List<List<String>> intersectionList = new ArrayList<>();
        boolean isPc = ServletUtil.getHeader("jnpf-origin").equals("pc");
        String columnData = !isPc ? ThemeFileConstant.getAppColumnData() : ThemeFileConstant.getColumnData();
        ColumnDataModel columnDataModel = JsonUtil.getJsonToBean(columnData, ColumnDataModel.class);
        String ruleJson = !isPc ? JsonUtil.getObjectToString(columnDataModel.getRuleListApp()) : JsonUtil.getObjectToString(columnDataModel.getRuleList());

        int total = 0;
        int themeFileNum = 0;
        QueryWrapper<ThemeFileEntity> themeFileQueryWrapper = new QueryWrapper<>();
        List<String> allSuperIDlist = new ArrayList<>();
        String superOp = "";
        if (ObjectUtil.isNotEmpty(themeFilePagination.getSuperQueryJson())) {
            List<String> allSuperList = new ArrayList<>();
            List<List<String>> intersectionSuperList = new ArrayList<>();
            String queryJson = themeFilePagination.getSuperQueryJson();
            SuperJsonModel superJsonModel = JsonUtil.getJsonToBean(queryJson, SuperJsonModel.class);
            int superNum = 0;
            QueryWrapper<ThemeFileEntity> themeFileSuperWrapper = new QueryWrapper<>();
            themeFileSuperWrapper = generaterSwapUtil.getCondition(new QueryModel(themeFileSuperWrapper, ThemeFileEntity.class, queryJson, "0"));
            int themeFileNum1 = themeFileSuperWrapper.getExpression().getNormal().size();
            if (themeFileNum1 > 0) {
                List<String> themeFileList = this.list(themeFileSuperWrapper).stream().map(ThemeFileEntity::getId).collect(Collectors.toList());
                allSuperList.addAll(themeFileList);
                intersectionSuperList.add(themeFileList);
                superNum++;
            }
            superOp = superNum > 0 ? superJsonModel.getMatchLogic() : "";
            //and or
            if (superOp.equalsIgnoreCase("and")) {
                allSuperIDlist = generaterSwapUtil.getIntersection(intersectionSuperList);
            } else {
                allSuperIDlist = allSuperList;
            }
        }
        List<String> allRuleIDlist = new ArrayList<>();
        String ruleOp = "";
        if (ObjectUtil.isNotEmpty(ruleJson)) {
            List<String> allRuleList = new ArrayList<>();
            List<List<String>> intersectionRuleList = new ArrayList<>();
            SuperJsonModel ruleJsonModel = JsonUtil.getJsonToBean(ruleJson, SuperJsonModel.class);
            int ruleNum = 0;
            QueryWrapper<ThemeFileEntity> themeFileSuperWrapper = new QueryWrapper<>();
            themeFileSuperWrapper = generaterSwapUtil.getCondition(new QueryModel(themeFileSuperWrapper, ThemeFileEntity.class, ruleJson, "0"));
            int themeFileNum1 = themeFileSuperWrapper.getExpression().getNormal().size();
            if (themeFileNum1 > 0) {
                List<String> themeFileList = this.list(themeFileSuperWrapper).stream().map(ThemeFileEntity::getId).collect(Collectors.toList());
                allRuleList.addAll(themeFileList);
                intersectionRuleList.add(themeFileList);
                ruleNum++;
            }
            ruleOp = ruleNum > 0 ? ruleJsonModel.getMatchLogic() : "";
            //and or
            if (ruleOp.equalsIgnoreCase("and")) {
                allRuleIDlist = generaterSwapUtil.getIntersection(intersectionRuleList);
            } else {
                allRuleIDlist = allRuleList;
            }
        }
        boolean pcPermission = false;
        boolean appPermission = false;
        if (isPc && pcPermission) {
            if (!userProvider.get().getIsAdministrator()) {
                Object themeFileObj = generaterSwapUtil.getAuthorizeCondition(new QueryModel(themeFileQueryWrapper, ThemeFileEntity.class, themeFilePagination.getMenuId(), "0"));
                if (ObjectUtil.isEmpty(themeFileObj)) {
                    return new ArrayList<>();
                } else {
                    themeFileQueryWrapper = (QueryWrapper<ThemeFileEntity>) themeFileObj;
                    if (themeFileQueryWrapper.getExpression().getNormal().size() > 0) {
                        themeFileNum++;
                    }
                }
            }
        }
        if (!isPc && appPermission) {
            if (!userProvider.get().getIsAdministrator()) {
                Object themeFileObj = generaterSwapUtil.getAuthorizeCondition(new QueryModel(themeFileQueryWrapper, ThemeFileEntity.class, themeFilePagination.getMenuId(), "0"));
                if (ObjectUtil.isEmpty(themeFileObj)) {
                    return new ArrayList<>();
                } else {
                    themeFileQueryWrapper = (QueryWrapper<ThemeFileEntity>) themeFileObj;
                    if (themeFileQueryWrapper.getExpression().getNormal().size() > 0) {
                        themeFileNum++;
                    }
                }


            }
        }
        if (isPc) {
            if (ObjectUtil.isNotEmpty(themeFilePagination.getFileid())) {
                themeFileNum++;

                String value = themeFilePagination.getFileid() instanceof List ? JsonUtil.getObjectToString(themeFilePagination.getFileid()) : String.valueOf(themeFilePagination.getFileid());
                themeFileQueryWrapper.lambda().like(ThemeFileEntity::getFileid, value);

            }

            if (ObjectUtil.isNotEmpty(themeFilePagination.getThemeid())) {
                themeFileNum++;

                String value = themeFilePagination.getThemeid() instanceof List ? JsonUtil.getObjectToString(themeFilePagination.getThemeid()) : String.valueOf(themeFilePagination.getThemeid());
                themeFileQueryWrapper.lambda().like(ThemeFileEntity::getThemeid, value);

            }

            if (ObjectUtil.isNotEmpty(themeFilePagination.getCreateuser())) {
                themeFileNum++;

                themeFileQueryWrapper.lambda().eq(ThemeFileEntity::getCreateuser, themeFilePagination.getCreateuser());

            }

            if (ObjectUtil.isNotEmpty(themeFilePagination.getCreatetime())) {
                themeFileNum++;

                List CreatetimeList = JsonUtil.getJsonToList(themeFilePagination.getCreatetime(), String.class);
                Long fir = Long.valueOf(String.valueOf(CreatetimeList.get(0)));
                Long sec = Long.valueOf(String.valueOf(CreatetimeList.get(1)));

                themeFileQueryWrapper.lambda().ge(ThemeFileEntity::getCreatetime, new Date(fir)).le(ThemeFileEntity::getCreatetime, DateUtil.stringToDate(DateUtil.daFormatYmd(sec) + " 23:59:59"));


            }

        }
        List<String> intersection = generaterSwapUtil.getIntersection(intersectionList);
        if (total > 0) {
            if (intersection.size() == 0) {
                intersection.add("jnpfNullList");
            }
            themeFileQueryWrapper.lambda().in(ThemeFileEntity::getId, intersection);
        }
        //是否有高级查询
        if (StringUtil.isNotEmpty(superOp)) {
            if (allSuperIDlist.size() == 0) {
                allSuperIDlist.add("jnpfNullList");
            }
            List<String> finalAllSuperIDlist = allSuperIDlist;
            themeFileQueryWrapper.lambda().and(t -> t.in(ThemeFileEntity::getId, finalAllSuperIDlist));
        }
        //是否有数据过滤查询
        if (StringUtil.isNotEmpty(ruleOp)) {
            if (allRuleIDlist.size() == 0) {
                allRuleIDlist.add("jnpfNullList");
            }
            List<String> finalAllRuleIDlist = allRuleIDlist;
            themeFileQueryWrapper.lambda().and(t -> t.in(ThemeFileEntity::getId, finalAllRuleIDlist));
        }

        //排序
        if (StringUtil.isEmpty(themeFilePagination.getSidx())) {
            themeFileQueryWrapper.lambda().orderByDesc(ThemeFileEntity::getId);
        } else {
            try {
                String sidx = themeFilePagination.getSidx();
                String[] strs = sidx.split("_name");
                ThemeFileEntity themeFileEntity = new ThemeFileEntity();
                Field declaredField = themeFileEntity.getClass().getDeclaredField(strs[0]);
                declaredField.setAccessible(true);
                String value = declaredField.getAnnotation(TableField.class).value();
                themeFileQueryWrapper = "asc".equals(themeFilePagination.getSort().toLowerCase()) ? themeFileQueryWrapper.orderByAsc(value) : themeFileQueryWrapper.orderByDesc(value);
            } catch (NoSuchFieldException e) {
                e.printStackTrace();
            }
        }

        if ("0".equals(dataType)) {
            if ((total > 0 && AllIdList.size() > 0) || total == 0) {
                Page<ThemeFileEntity> page = new Page<>(themeFilePagination.getCurrentPage(), themeFilePagination.getPageSize());
                IPage<ThemeFileEntity> userIPage = this.page(page, themeFileQueryWrapper);
                return themeFilePagination.setData(userIPage.getRecords(), userIPage.getTotal());
            } else {
                List<ThemeFileEntity> list = new ArrayList();
                return themeFilePagination.setData(list, list.size());
            }
        } else {
            return this.list(themeFileQueryWrapper);
        }
    }

    @Override
    public ThemeFileEntity getInfo(String id) {
        QueryWrapper<ThemeFileEntity> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(ThemeFileEntity::getId, id);
        return this.getOne(queryWrapper);
    }

    @Override
    public void create(ThemeFileEntity entity) {
        this.save(entity);
    }

    @Override
    public boolean update(String id, ThemeFileEntity entity) {
        return this.updateById(entity);
    }

    @Override
    public void delete(ThemeFileEntity entity) {
        if (entity != null) {
            this.removeById(entity.getId());
        }
    }

    /**
     * 验证表单唯一字段，正则，非空 i-0新增-1修改
     */
    @Override
    public String checkForm(ThemeFileForm form, int i) {
        boolean isUp = StringUtil.isNotEmpty(form.getId()) && !form.getId().equals("0");
        String id = "";
        String countRecover = "";
        if (isUp) {
            id = form.getId();
        }
        //主表字段验证
        return countRecover;
    }

    /**
     * 新增修改数据(事务回滚)
     *
     * @param id
     * @param themeFileForm
     * @return
     */
    @Override
    @Transactional
    public void saveOrUpdate(ThemeFileForm themeFileForm, String id, boolean isSave) throws Exception {
        UserInfo userInfo = userProvider.get();
        UserEntity userEntity = generaterSwapUtil.getUser(userInfo.getUserId());
        themeFileForm = JsonUtil.getJsonToBean(generaterSwapUtil.swapDatetime(ThemeFileConstant.getFormData(), themeFileForm), ThemeFileForm.class);
        ThemeFileEntity entity = JsonUtil.getJsonToBean(themeFileForm, ThemeFileEntity.class);

        if (isSave) {
            String mainId = RandomUtil.uuId();
            entity.setCreateuser(userInfo.getUserId());
            entity.setCreatetime(DateUtil.getNowDate());
            entity.setId(mainId);
        } else {
            entity.setCreateuser(userInfo.getUserId());
            entity.setCreatetime(DateUtil.getNowDate());
        }
        this.saveOrUpdate(entity);

    }

    @Override
    @Transactional
    public void bindThemeToFile(List<ThemeBound> themeIds, String fileId) {
        UserInfo userInfo = userProvider.get();
        // 先删除该文件和指定主题的绑定信息
        QueryWrapper<ThemeFileEntity> deleteWrapper = new QueryWrapper<>();
        deleteWrapper.eq("FILEID", fileId);
        // 提取需要删除的主题 ID 列表
        List<String> deleteThemeIdList = themeIds.stream().filter(t -> "2".equals(t.getType())) // 只处理标记为删除的记录
                .map(ThemeBound::getThemeid).collect(Collectors.toList());
        if (!deleteThemeIdList.isEmpty()) {
            deleteWrapper.in("THEMEID", deleteThemeIdList);
            // 新增节点ID过滤条件
            List<String> deleteNodeIdList = themeIds.stream()
                .filter(t -> "2".equals(t.getType()))
                .map(ThemeBound::getNodeid)
                .collect(Collectors.toList());
            deleteWrapper.in("NODEID", deleteNodeIdList);
            this.remove(deleteWrapper);
        }

        // 处理更新和新增的记录
        List<ThemeFileEntity> entityList = new ArrayList<>();
        for (ThemeBound themeFileUpReq : themeIds) {
            String type = themeFileUpReq.getType();
            if ("1".equals(type)) { // 更新
                QueryWrapper<ThemeFileEntity> updateWrapper = new QueryWrapper<>();
                updateWrapper.eq("FILEID", fileId).eq("THEMEID", themeFileUpReq.getThemeid());
                ThemeFileEntity entity = this.getOne(updateWrapper);
                if (entity != null) {
                    entity.setNodeid(themeFileUpReq.getNodeid());
                    entityList.add(entity);
                }
            } else if ("3".equals(type)) { // 新增
                ThemeFileEntity entity = new ThemeFileEntity();
                entity.setFileid(fileId);
                entity.setThemeid(themeFileUpReq.getThemeid());
                entity.setNodeid(themeFileUpReq.getNodeid());
                entity.setCreateuser(userInfo.getUserId()); // 添加创建人
                entity.setCreatetime(new Date()); // 添加创建时间
                entityList.add(entity);
            }
        }

        // 批量保存
        if (!entityList.isEmpty()) {
            this.saveOrUpdateBatch(entityList);
        }
    }


    @Override
    public List<String> getThemesByFileId(String fileId) {
        QueryWrapper<ThemeFileEntity> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("FILEID", fileId);
        List<ThemeFileEntity> entityList = this.list(queryWrapper);

        if (entityList.isEmpty()) {
            return Collections.emptyList();
        }

        List<String> themeIds = new ArrayList<>();
        for (ThemeFileEntity entity : entityList) {
            themeIds.add(entity.getThemeid());
        }
        return themeIds;
    }

    @Override
    public void deleteByIds(ArrayList<String> errorIds) {
        if (!errorIds.isEmpty()) {
            QueryWrapper<ThemeFileEntity> queryWrapper = new QueryWrapper<>();
            queryWrapper.in("fileid", errorIds);
            this.remove(queryWrapper);
        }
    }

    @Override
    public Long getCountByThemeId(String themeId) {
        QueryWrapper<ThemeFileEntity> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("THEMEID", themeId);
        return this.count(queryWrapper);
    }

    @Override
    public Long getCountById(String id) {
        QueryWrapper<ThemeFileEntity> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("NODEID", id);
        return this.count(queryWrapper);
    }
}
